package com.flute.tools.util.math;

import com.flute.tools.util.collection.Accumulator;

public class Probability {

	public static double getNormalDistribution(double expectation,
			double svariance, double value) {
		if (svariance == 0) {
			if (value == expectation) {
				return 1;
			} else {
				return 0;
			}
		} else {
			double pow = Math.pow((value - expectation), 2)
					/ (2 * Math.pow(svariance, 2));
			return 1 / (Math.sqrt(2 * Math.PI) * svariance)
					* Math.pow(Math.E, -pow);
		}
	}

	public static double getStanrdVariance(Double[] doubles) {
		return Math.sqrt(getVariance(doubles));
	}

	public static double getVariance(Double[] doubles) {
		if (doubles.length > 0) {
			double total = 0;
			for (double d : doubles) {
				total = total + d;
			}
			double average = total / Double.valueOf(doubles.length);
			total = 0;
			for (double d : doubles) {
				total = total + (average - d) * (average - d);
			}
			return total / Double.valueOf(doubles.length);
		} else {
			return -1;
		}
	}

	public static double getExpectation(Double[] doubles) {
		if (doubles.length > 0) {
			Accumulator<Double> map = new Accumulator<Double>();
			for (double d : doubles) {
				map.addKey(d);
			}
			double total = 0;
			for (double d : map.getKeys()) {
				total = total
						+ d
						* (Double.valueOf(map.getCount(d)) / Double.valueOf(map
								.getAllCount()));
			}
			return total;
		} else {
			return -1;
		}
	}
}
